package com.zxbg.service.impl.systemtoolsServiceImpl;

import com.alibaba.fastjson.JSON;
import com.alibaba.fastjson.JSONObject;
import com.zxbg.dao.DepartmentDao;
import com.zxbg.dao.EmployeeDao;
import com.zxbg.dao.InfoBlockDao;
import com.zxbg.dao.InfoBlockTypeDao;
import com.zxbg.domain.Department;
import com.zxbg.domain.Employee;
import com.zxbg.domain.InfoBlock;
import com.zxbg.service.impl.proportalServiceImpl.PIndexServiceImpl;
import com.zxbg.service.systemtoolsService.InfoBlockService;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.stereotype.Service;

import java.text.ParseException;
import java.text.SimpleDateFormat;
import java.util.*;

@Service
public class InfoBlockServiceImpl implements InfoBlockService {
    @Autowired
    InfoBlockDao infoBlockDao;
    @Autowired
    InfoBlockTypeDao infoBlockTypeDao;
    @Autowired
    EmployeeDao employeeDao;
    @Autowired
    OrganizationalStructureServiceImpl organizationalStructureService;
    @Autowired
    DepartmentDao departmentDao;
    @Autowired
    PIndexServiceImpl pIndexService;

    @Override
    public List<InfoBlock> getListByModuleId(String info_module_id, Integer tenant_id, Map<String, Object> search_info, String employee_id) {
        String mode = (String) search_info.get("mode");
        List<InfoBlock> infoBlockList = new ArrayList<>();
        if(mode.equals("all")) {
            infoBlockList = infoBlockDao.getListByModuleId(info_module_id, tenant_id);
        } else if(mode.equals("personal")) {
            if(info_module_id.equals("NewManage")) {
                infoBlockList = pIndexService.getActiveNews(employee_id, tenant_id);
            } else if(info_module_id.equals("NoticesManage")) {
                infoBlockList = pIndexService.getActiveNotices(employee_id, tenant_id);
            } else if(info_module_id.equals("RulesManage")) {
                infoBlockList = pIndexService.getActiveRegulation(employee_id, tenant_id);
            }
        }
        List<InfoBlock> preList = new ArrayList<>();
        Integer type_id = search_info.get("classify").equals("") ? -1 : (Integer)search_info.get("classify");
        SimpleDateFormat formatter = new SimpleDateFormat("yyyy-MM-dd");
        Date start_create_time = null;
        Date end_create_time = null;
        String jsonObject = JSON.toJSONString(search_info.get("creator"));
        String creator_id = JSONObject.parseObject(jsonObject, Employee.class).getEmployee_id();
        if(((ArrayList)search_info.get("createTime")).size() != 0) {
            try {
                start_create_time = formatter.parse((String)((ArrayList)search_info.get("createTime")).get(0));
                end_create_time = formatter.parse((String)((ArrayList)search_info.get("createTime")).get(1));
            } catch (ParseException e) {
                e.printStackTrace();
            }
        }
        for (int i = 0; i < infoBlockList.size(); i++) {
            InfoBlock tempBlock = infoBlockList.get(i);
            tempBlock.setType(infoBlockTypeDao.getBlockTypeByTypeId(tempBlock.getType_id()));
            if(new Date().after(tempBlock.getStart_time()) && tempBlock.getStatus() != 2 && tempBlock.getStatus() != 0 && tempBlock.getStatus() != 1) {
                infoBlockDao.setBlockRun(tempBlock.getId());
            }
            if(tempBlock.getEnd_time() != null && new Date().after(tempBlock.getEnd_time()) && tempBlock.getStatus() != 1 && tempBlock.getStatus() != 0) {
                changeIsTop(tempBlock.getId(), 0);
                infoBlockDao.setBlockStop(tempBlock.getId());
            }
            if(type_id != -1 && tempBlock.getType_id() != type_id) {
                continue;
            }
            if(!search_info.get("title").equals("") && !tempBlock.getTitle().contains((String)search_info.get("title"))) {
                continue;
            }
            if(start_create_time != null && (tempBlock.getCreate_time().before(start_create_time) || tempBlock.getCreate_time().after(end_create_time))) {
                continue;
            }
            if(creator_id != null && !tempBlock.getCreator_id().equals(creator_id)) {
                continue;
            }
            Set<Employee> allCanView = new HashSet<>();
            if(!tempBlock.getPublic_range().equals("all")) {
                Map<String, Object> map = getPublicRangeRealInfo(tempBlock, tenant_id);
                tempBlock.setRange(map);
                List<Department> departmentList = (List<Department>) map.get("dept");
                for (Department department : departmentList) {
                    Map<String, Object> searchInfo = new HashMap<>();
                    search_info.put("worker_id", department.getWorker_id());
                    search_info.put("status", 1);
                    allCanView.addAll(organizationalStructureService.getEmployeesByWorkerId(search_info, tenant_id));
                }
                allCanView.addAll((List<Employee>) map.get("employee"));
            } else {
                allCanView.addAll(employeeDao.getAllUseEmployee(tenant_id));
            }
            tempBlock.setCreator(organizationalStructureService.getAllKindsDept(employeeDao.getEmployeeByEmployeeId(tempBlock.getCreator_id(), tenant_id)));
            String viewedString = tempBlock.getViewed_employee_id();
            List<Employee> viewedEmp = new ArrayList<>();
            List<String> viewed = new ArrayList<>();
            if(viewedString != null && !viewedString.equals("")) {
                viewed = Arrays.asList(viewedString.split(","));
                for (String emp : viewed) {
                    Employee currentE = employeeDao.getEmployeeByEmployeeId(emp, tenant_id);
                    viewedEmp.add(currentE);
                }
            }
            tempBlock.setViewed_employee(viewedEmp);
            List<Employee> unViewed = new ArrayList<>();
            for (Employee employee : new ArrayList<>(allCanView)) {
                if(!viewed.contains(employee.getEmployee_id())) {
                    unViewed.add(employee);
                }
            }
            tempBlock.setUn_viewed_employee(unViewed);
            preList.add(tempBlock);
        }
        return getTopOrderList(preList);
    }

    public List<InfoBlock> getTopOrderList(List<InfoBlock> preList) {
        List<InfoBlock> resList = new ArrayList<>();
        for (int i = preList.size() - 1; i >= 0; i--) {
            if(preList.get(i).getIs_top() == 1 && preList.get(i).getStatus() == 2) {
                resList.add(preList.get(i));
            }
        }
        for (int i = 0; i < preList.size(); i++) {
            if(preList.get(i).getIs_top() == 0 || (preList.get(i).getIs_top() == 1 && preList.get(i).getStatus() != 2)) {
                resList.add(preList.get(i));
            }
        }
        return resList;
    }

    public Map<String, Object> getPublicRangeRealInfo(InfoBlock infoBlock, Integer tenant_id) {
        List<Employee> employeeList = new ArrayList<>();
        List<Department> departmentList = new ArrayList<>();
        String[] employeeIdList = infoBlock.getPublic_range().split(" & ");
        for (int j = 0; j < employeeIdList.length; j++) {
            if(j == 0) {
                String[] deptList = employeeIdList[j].split("、");
                boolean firstDept = true;
                for (int k = 0; k < deptList.length; k++) {
                    try {
                        Department tempD = departmentDao.getDeptById(Integer.parseInt(deptList[k]));
                        if(tempD != null) {
                            departmentList.add(tempD);
                        } else {
                            if(k == 0) {
                                firstDept = false;
                            }
                        }
                    } catch (Exception e) {
                        firstDept = false;
                        break;
                    }
                }
                if(firstDept) {
                    continue;
                }
            }
            employeeList.add(employeeDao.getEmployeeByEmployeeId(employeeIdList[j], tenant_id));
        }
        infoBlock.setPublic_range("part");
        Map<String, Object> resMap = new HashMap<>();
        resMap.put("dept", departmentList);
        resMap.put("employee", employeeList);
        return resMap;
    }

    @Override
    public boolean addInfoBlock(InfoBlock infoBlock) {
        if(infoBlock.getStatus() == -1) {
            if(new Date().after(infoBlock.getStart_time())) {
                infoBlock.setStatus(2);
                infoBlock.setClick_num(0);
            }
            if(new Date().before(infoBlock.getStart_time())) {
                infoBlock.setStatus(3);
            }
            if(infoBlock.getEnd_time() != null && new Date().after(infoBlock.getEnd_time())) {
                infoBlock.setStatus(1);
            }
        }
        infoBlock.setCreate_time(new Date());
        return infoBlockDao.addInfoBlock(infoBlock) > 0;
    }

    @Override
    public boolean stopInfoBlock(Integer[] ids) {
        for (int i = 0; i < ids.length; i++) {
            InfoBlock temp = infoBlockDao.getInfoBlockById(ids[i]);
            if(temp.getStatus() == 0) {
                return false;
            }
            changeIsTop(ids[i], 0);
            infoBlockDao.stopInfoBlock(ids[i]);
        }
        return true;
    }

    @Override
    public boolean changeIsTop(Integer id, Integer is_top) {
        return infoBlockDao.changeIsTop(id, is_top) > 0;
    }

    @Override
    public boolean deleteInfoBlock(Integer id) {
        return infoBlockDao.deleteInfoBlock(id) > 0;
    }

    @Override
    public boolean publishInfoBlock(Integer id) {
        InfoBlock infoBlock = infoBlockDao.getInfoBlockById(id);
        if(new Date().after(infoBlock.getStart_time())) {
            infoBlock.setStatus(2);
        }
        if(new Date().before(infoBlock.getStart_time())) {
            infoBlock.setStatus(3);
        }
        if(infoBlock.getEnd_time() != null && new Date().after(infoBlock.getEnd_time())) {
            return false;
        }
        return infoBlockDao.publishInfoBlock(id, infoBlock.getStatus()) > 0;
    }

    @Override
    public boolean useRightNow(Integer[] ids) {
        boolean ifSuccess = true;
        for (int i = 0; i < ids.length; i++) {
            InfoBlock temp = infoBlockDao.getInfoBlockById(ids[i]);
            if(temp.getEnd_time() == null || (temp.getEnd_time() != null && new Date().before(temp.getEnd_time()))) {
                infoBlockDao.setBlockStartTimeNow(ids[i]);
                if(temp.getClick_num() != null) {
                    infoBlockDao.setBlockReRun(ids[i]);
                } else {
                    infoBlockDao.setBlockRun(ids[i]);
                }
            } else {
                ifSuccess = false;
            }
        }
        return ifSuccess;
    }

    @Override
    public boolean updateInfoBlock(InfoBlock infoBlock) {
        return infoBlockDao.updateInfoBlock(infoBlock) > 0;
    }
}
